package com.xiaoma.suanfa;

import java.util.Arrays;

/**
 * @author xiaomacdut
 * @date 2020年3月10日 下午1:35:15
 */
public class QuickSort {
    
    public static void main(String [] args){
        
        int[] arr = {7, 5, 3, 2, 4, 1, 8, 9, 6};
        
        // 快速排序
        int low = 0;
        int high = arr.length - 1;
        quickSort1(arr, low, high);

        System.out.println(Arrays.toString(arr));
    }
    
    public static void quickSort(int [] arr, int low, int high){
        // 如果指针在同一位置(只有一个数据时)，退出
        if(high - low < 1){
            return;
        }
        // 标记，从高指针开始，还是低指针（默认高指针）
        boolean flag = true;
        // 记录指针的其实位置
        int start = low;
        int end = high;
        // 默认中间值为低指针的第一个值
        int midValue = arr[low];
        while(true){
            // 高指针移动
            if(flag){
                // 如果列表右方的数据大于中间值，则向左移动
                if(arr[high] > midValue){
                    high--;
                }else if(arr[high] < midValue){
                    // 如果小于，则覆盖最开始的低指针值，并且移动低指针，标志位改成从低指针开始移动
                    arr[low] = arr[high];
                    low++;
                    flag = false;
                }
            }else{
                // 如果低指针数据小于中间值，则低指针向右移动
                if(arr[low] < midValue){
                    low++;
                }else if(arr[low] > midValue){
                    // 如果低指针的值大于中间值，则覆盖高指针停留时的数据，并向左移动高指针。切换为高指针移动
                    arr[high] = arr[low];
                    high--;
                    flag = true;
                }
            }
            // 当两个指针的位置相同时，则找到了中间值的位置，并退出循环
            if(low == high){
                arr[low] = midValue;
                break;
            }
        }
        // 然后出现有，中间值左边的小于中间值。右边的大于中间值。
        // 然后在对左右两边的列表在进行快速排序
        quickSort(arr, start, low - 1);
        quickSort(arr, low + 1, end);
    }

    public static void quickSort1(int[] a, int l, int r) {

        if (l < r) {
            int i,j,x;

            i = l;
            j = r;
            x = a[i];
            while (i < j) {
                while(i < j && a[j] > x)
                    j--; // 从右向左找第一个小于x的数
                if(i < j)
                    a[i++] = a[j];
                while(i < j && a[i] < x)
                    i++; // 从左向右找第一个大于x的数
                if(i < j)
                    a[j--] = a[i];
            }
            a[i] = x;
            quickSort(a, l, i-1); /* 递归调用 */
            quickSort(a, i+1, r); /* 递归调用 */
        }
    }
}
